#include "utils.h"

namespace Utils {
QString ConvertPath(QString &originPath)
{
    return originPath.remove(0, 8);
}

gp_Pnt BndBoxCoords::center() const
{
    return {
        (this->xmax + this->xmin) / 2.,
        (this->ymax + this->ymin) / 2.,
        (this->zmax + this->zmin) / 2.
    };
}

std::array<gp_Pnt, 8> BndBoxCoords::vertices() const
{
    return {{
        { this->xmin, this->ymin, this->zmax },
        { this->xmax, this->ymin, this->zmax },
        { this->xmin, this->ymin, this->zmin },
        { this->xmax, this->ymin, this->zmin },
        { this->xmin, this->ymax, this->zmax },
        { this->xmax, this->ymax, this->zmax },
        { this->xmin, this->ymax, this->zmin },
        { this->xmax, this->ymax, this->zmin }
    }};
}

gp_Pnt BndBoxCoords::minVertex() const
{
    return { this->xmin, this->ymin, this->zmin };
}

gp_Pnt BndBoxCoords::maxVertex() const
{
    return { this->xmax, this->ymax, this->zmax };
}

BndBoxCoords BndBoxCoords::get(const Bnd_Box& box)
{
    BndBoxCoords bbc = {};
    if (!box.IsVoid())
        box.Get(bbc.xmin, bbc.ymin, bbc.zmin, bbc.xmax, bbc.ymax, bbc.zmax);
    return bbc;
}

void BndUtils::add(Bnd_Box* box, const Bnd_Box& other)
{
    const auto bbc = BndBoxCoords::get(other);
    for (const gp_Pnt& pnt : bbc.vertices())
        box->Add(pnt);
}

bool BndUtils::isOpen(const Bnd_Box& bndBox)
{
    return bndBox.IsOpen();
}

bool BndUtils::hasFinitePart(const Bnd_Box& bndBox)
{
    return bndBox.HasFinitePart();
}

Bnd_Box BndUtils::finitePart(const Bnd_Box& bndBox)
{
    return bndBox.FinitePart();
}

Bnd_Box BndUtils::AisObject_boundingBox(const Handle(AIS_InteractiveObject)& object)
{
    Bnd_Box box;
    if (object.IsNull())
        return box;

    for (Handle_PrsMgr_Presentation prs : object->Presentations()) {
        if (prs->Mode() == object->DisplayMode() && !prs->CStructure()->BoundingBox().IsValid())
            prs->CalculateBoundBox();
    }

    object->BoundingBox(box);
    return box;
}

TopLoc_Location XCaf::shapeReferenceLocation(const TDF_Label& lbl)
{
    return XCAFDoc_ShapeTool::GetLocation(lbl);
}

TopLoc_Location XCaf::shapeAbsoluteLocation(TDF_Label& rootNodeLabel, TDF_Label& nodeLabel)
{

    TopLoc_Location absoluteLoc;

    const TopLoc_Location nodeLoc = XCaf::shapeReferenceLocation(nodeLabel);
    absoluteLoc = nodeLoc * absoluteLoc;

    return absoluteLoc;
}

}
